<!--
 * @Author: 吴世扬 18368095041@163.com
 * @Date: 2024-04-25 08:58:59
 * @LastEditors: 吴世扬 18368095041@163.com
 * @LastEditTime: 2025-02-05 17:28:00
 * @FilePath: /vue3-admin/src/components/ui/JsonEditor/JsonEditor.vue
 * @Description: 这是默认设置,请设置`customMade`, 打开koroFileHeader查看配置 进行设置: https://github.com/OBKoro1/koro1FileHeader/wiki/%E9%85%8D%E7%BD%AE
-->
<script lang="ts" setup>
import { ref, toRefs, watchEffect, onMounted, onUnmounted } from 'vue';
import 'jsoneditor/src/scss/jsoneditor.scss';
import { useDebounceFn } from '@vueuse/core';
import JSONEditor, { type JSONEditorMode } from 'jsoneditor';

const props = defineProps<{
    modelValue?: string;
}>();
const emits = defineEmits<{
    (event: 'update:model-value', value: string): void;
}>();
const { modelValue } = toRefs(props);
const id = 'jsoneditor' + Date.now();
const value = ref('');
const options = ref({
    modes: [
        'code',
        'form',
        'text',
        'tree',
        'view',
        'preview'
    ] as JSONEditorMode[], // allowed modes
    mode: 'tree' as JSONEditorMode,
    onModeChange: function (newMode: string, oldMode: string) {
        console.log('Mode switched from', oldMode, 'to', newMode);
    },
    onChangeText: (jsonString: string) => {
        // console.log(jsonString);
        value.value = jsonString;
        emits('update:model-value', jsonString);
    }
});

let editor = ref();
const debounceUpdate = useDebounceFn((val: string) => {
    editor.value.set(val);
}, 1000);

watchEffect(() => {
    if (editor.value) {
        if (modelValue.value !== value.value) {
            try {
                if (modelValue.value) {
                    const json = JSON.parse(modelValue.value);
                    debounceUpdate(json);
                }
            } catch (error) {
                console.log('Invalid JSON string');
            }
        }
    }
});
const divRef = ref<HTMLDivElement | null>(null);
onMounted(() => {
    if (divRef.value) {
        editor.value = new JSONEditor(divRef.value, options.value);
    }
});
onUnmounted(() => {
    editor.value.destroy();
});
</script>

<template>
    <div class="jsoneditor-container">
        <div :id="id" ref="divRef" style="width: 100%; height: 100%"></div>
    </div>
</template>

<style lang="scss" scoped>
.jsoneditor-container {
    width: 100%;
    height: 100%;
}
</style>
